import regeneratorRuntime from '../resource/libs/runtime'
import QQMapWX from '../resource/libs/qqmap-wx-jssdk'
import { qq_map_key, tab_pages_path } from './config'

/**使用 promise 包装微信的异步 api 接口调用（兼容腾讯位置服务 api 接口调用）；
 * 接口调用成功，触发 resolve 传递返回值；
 * 接口调用失败，打印错误消息，并触发 resolve 传递 null；
 * @param {Function} api 微信的异步 api 接口，比如 wx.login
 * @param {Object} [options={}] 调用接口要传的参数对象，这里会屏蔽其中的三个回调函数
 * @returns 包装后的 Promise 对象
 */
const wxApiPromise = (api, options = {}) => {
  let { success, fail, complete, ...other } = options
  if (success || fail || complete) {
    throw new Error('success, fail, complete 回调函数已经被屏蔽，请查阅 wxApiPromise 函数')
  }
  return new Promise(resolve => {
    api({
      ...other,
      success (res) {
        resolve(res)
      },
      fail (res) {
        let { errMsg, errCode, message } = res
        let msg = errMsg || message
        console.error(msg)
        resolve(null)
      }
    })
  })
}

// 实例化腾讯位置服务微信小程序 JavaScript SDK 的 API 核心类
// 详情参考相关文档（https://lbs.qq.com/index.html）
const qq_map = new QQMapWX({ key: qq_map_key })
// 基于腾讯位置服务根据坐标转换地理位置信息和附近poi列表；
const asyncReverseGeocoder = async (options) => {
  let res = await wxApiPromise(qq_map.reverseGeocoder.bind(qq_map), options)
  return res // 调用失败时返回 null
}
// 基于腾讯位置服务用于获取输入关键字的补完与提示；
const asyncGetSuggestion = async (options) => {
  let res = await wxApiPromise(qq_map.getSuggestion.bind(qq_map), options)
  return res
}
// 基于腾讯位置服务计算一个点到多点的步行、驾车距离；
const asyncCalculateDistance = async (options) => {
  let res = await wxApiPromise(qq_map.calculateDistance.bind(qq_map), options)
  return res
}

/**同步缓存当前页面的 url 信息；
 * key 为 'origin_page'
 * value 为 {route,options}
 *          参考模拟器底下的页面路径和页面参数
 */
const syncCacheCurrentUrl = () => {
  let current = getCurrentPages().pop()
  wx.setStorageSync('origin_page', {
    route: current.route,
    options: current.options
  })
}

// 根据缓存的页面 url 信息，跳转回原来的页面
const redirectBack = () => {
  let origin_page = wx.getStorageSync('origin_page')
  // 清除缓存的原页面 url 信息
  wx.removeStorageSync('origin_page')
  let route = '/' + origin_page.route
  if (tab_pages_path.indexOf(route) !== -1) {
    // tab 页
    wx.switchTab({
      url: route
    })
  } else {
    // 非 tab 页
    let url = `${route}?`
    let options = origin_page.options
    for (let key in options) {
      url += `${key}=${options[key]}&`
    }
    wx.redirectTo({
      url: url.substring(0, url.length - 1)
    })
  }
}

const keepDecimal = (number, decimalPoint = 6) => {
  if(typeof decimalPoint !== 'number'){
    decimalPoint = 6
  }else if(decimalPoint < 0){
    decimalPoint = 0
  }
  try {
    const reg = new RegExp(`^([0-9]+\.[0-9]{${decimalPoint}})([0-9]+)$`)
    number = String(number).replace(reg, ($$, $1) => $1)
  } catch (e) {
    number = 0
  }
  return Number(number)
}

const transformFromBaiduToGCJ = (latitude, longitude) => {
  var xPi = 3.14159265358979323846264338327950288 * 3000.0 / 180.0;

  var x = longitude - 0.0065;
  var y = latitude - 0.006;
  var z = Math.sqrt(x * x + y * y) - 0.00002 * Math.sin(y * xPi);
  var theta = Math.atan2(y, x) - 0.000003 * Math.cos(x * xPi);
  var a_latitude = z * Math.sin(theta);
  var a_longitude = z * Math.cos(theta);

  return { latitude: a_latitude, longitude: a_longitude };
}

const compare = (obj1, obj2) => {
  return JSON.stringify(obj1) === JSON.stringify(obj2)
}

export {
  wxApiPromise,
  asyncReverseGeocoder,
  asyncGetSuggestion,
  asyncCalculateDistance,
  syncCacheCurrentUrl,
  redirectBack,
  transformFromBaiduToGCJ,
  compare
}
